#pragma once
// #include "Reactor_pool.hpp"
#include "Connection.hpp"
#include "Parse.hpp"
#include "Reactor.hpp"
#include <vector>
#include <memory>
#include <queue>
// #include "BasePoll.hpp"

// class Reactor_pool;
class Eventfd : public Connection
{
public:
    Eventfd(int eventfd)
    {
        SetSockfd(eventfd);
        SetEvents(EPOLLIN | EPOLLET);
        parse.RegisterCal([&](const request &req)
                          { return cal.Execute(req); });
    }
    virtual void Sender()
    {
    }
    virtual void Recver()
    {
        // 当被通知读就绪时，读取四个字节

        // 2.获取对应的Reactor的Reactor_pool指向的队列，然后这里调用这个GetOwner就是他的父类了，不涉及到交叉包含了，
        std::queue<int> queue = GetOwner()->GetOwner()->GetQueue();
        // 3.从队列中pop出sockfd
        for (int i = 0; i < queue.size(); i++)
        {
            int sockfd = queue.front();
            auto coon = std::make_shared<ioservice>(sockfd);
            coon->RegisterFunc([&](std::string packge)
                               { return parse.HandlerBuffer(packge); }); // 将处理的接口注册给ioservice

            GetOwner()->InsertConnection(coon); // 每次读取sockfd，都将sockfd交给当前Reactor关心
        }
    }
    void Write(int value) // 向eventfd中写入
    {
        write(_sockfd, &value, sizeof(value));
    }
    virtual void Excepter()
    {
    }

    ~Eventfd()
    {
        if (_sockfd > 0)
        {
            ::close(_sockfd);
        }
    }

private:
    Calculator cal;
    Parse parse;
};

/**
 * 同学，我在想，你的这个项目，他其实都是头文件的项目，如果采用我刚说的第一种方式，其实就多了两个源文件，
 * 那么你其他的代码在使用这个库的时候，不仅仅是要包含头文件，还需要链接库，其实就很突兀
 * 
 * 我就采用第二种把，很方便，
 * 
 * 我先跟你说一下噢，这个头文件中用到了这个Reactor_pool类型，然后在这个Reactor_pool头文件中包含了Eventfd这个头文件
 * 这个是造成这个问题的原因
 * 
 * 你虽然可以不用去包含Reactor_pool这个头文件，做一个前置声明，但是前置声明的类名不能支撑他的指针调用成员函数，因为他不认识这个成员函数
 * 这个能理解噢，
 * 
 * 现在的思路呢就是去写一个Reactor_poll这个类的父类，或者是eventfd的父类，让对让去拥有这个父类的类型指针，然后暴露出接口就可以了，
 * 
 * 我看看要写那个类的父类会简单一些
 * 
 * 因为eventfd其实是有父类的，就是connection，那就写一个reactorpool的父类把
 * 
 * 现在把这个文件改造一下就可以了
 * 
*/